﻿using System;
using System.Collections.Generic;
using System.Linq;
using System.Security.Claims;
using System.Text;
using System.Threading.Tasks;
using Foundation.Core;

namespace Dyao.Book.Core
{
    //
    // 摘要:
    //     Thread Current Principal Accessor
    public class ThreadCurrentPrincipalAccessor : ICurrentPrincipalAccessor, ISingletonDependency
    {
        private readonly AsyncLocal<ClaimsPrincipal> _currentPrincipal = new AsyncLocal<ClaimsPrincipal>();

        public ClaimsPrincipal Principal => _currentPrincipal.Value ?? GetClaimsPrincipal();

        //
        // 摘要:
        //     Get claims principal from Thread.CurrentPrincipal
        protected virtual ClaimsPrincipal GetClaimsPrincipal()
        {
            return Thread.CurrentPrincipal as ClaimsPrincipal;
        }

        //
        // 摘要:
        //     Change claims principal
        //
        // 参数:
        //   principal:
        //     The claims principal need to change
        public virtual IDisposable Change(ClaimsPrincipal principal)
        {
            return SetCurrent(principal);
        }

        //
        // 摘要:
        //     Set current claims principal
        //
        // 参数:
        //   principal:
        //     The claims principal need to change
        private IDisposable SetCurrent(ClaimsPrincipal principal)
        {
            ClaimsPrincipal parent = Principal;
            _currentPrincipal.Value = principal;
            return new DisposeAction(delegate
            {
                _currentPrincipal.Value = parent;
            });
        }
    }
}
